#include "server_h.h"

void handler(int sig){
    wait(NULL);
}

void do_client(int acceptfd,sqlite3* db){
    MSG msg;
    while(recv(acceptfd,&msg,sizeof(msg),0)>0){
        switch(msg.type)
        {
        case R:
            do_register(acceptfd,&msg,db);
            break;
        case L:
            do_login(acceptfd,&msg,db);
            break;
        case S:
            do_select(acceptfd,&msg,db);
            break;
        case H:
            do_history(acceptfd,&msg,db);
            break;
        default:
            printf("数据非法\n");
        }
    }

    printf("客户端退出\n");
    close(acceptfd);
    pthread_exit(0);
}

void do_register(int acceptfd,MSG* msg,sqlite3* db){
    char *errmsg=NULL;
    char sql[128]={0};
    sprintf(sql,"insert into usr values('%s','%s');",msg->name,msg->pass);
    
    memset(msg->text,0,sizeof(msg->text));
    if(sqlite3_exec(db,sql,NULL,NULL,&errmsg)!=SQLITE_OK){
        printf("注册失败:%s\n",errmsg);
        strcpy(msg->text,"NO");
    }else{
        printf("注册成功\n");
        strcpy(msg->text,"KO");
    }

    if(send(acceptfd,msg,sizeof(MSG),0)==-1){
        ERRLOG("send error");
    }

}

void do_login(int acceptfd,MSG* msg,sqlite3* db){
    char * errmsg=NULL;
    char sql[128]={0};
    char **ret=NULL;
    int nrow,ncolumn;
    sprintf(sql,"select * from usr where name='%s' and pass='%s';",msg->name,msg->pass);

    memset(msg->text,0,sizeof(msg->text));
    if(sqlite3_get_table(db,sql,&ret,&nrow,&ncolumn,&errmsg)!=SQLITE_OK){
        printf("查询数据失败:%s\n",errmsg);
        ERRLOG("sqlite3_get_table error");
    }else{
        if(nrow==1){
            strcpy(msg->text,"KO");
            printf("登录成功\n");
        }else{
            strcpy(msg->text,"NO");
            printf("登录失败\n");
        }
    }

    if(send(acceptfd,msg,sizeof(MSG),0)==-1){
        ERRLOG("send error");
    }

}

void do_select(int acceptfd,MSG* msg,sqlite3* db){
    char word[32]={0};
    int found=0;
    char time[64]={0};
    char sql[128]={0};
    char *errmsg;

    strcpy(word,msg->text);

    found=do_searchword(acceptfd,msg,word);

    if(found==1){
        do_time(time);

        sprintf(sql,"insert into record values('%s','%s','%s');",msg->name,time,word);
        
        if(sqlite3_exec(db,sql,NULL,NULL,&errmsg)!=SQLITE_OK){
            ERRLOG("sqlite3_exec error");
        }

    }else{
        strcpy(msg->text,"没有找到此单词");
    }

    if(send(acceptfd,msg,sizeof(MSG),0)==-1){
        ERRLOG("send error");
    }
}

int do_searchword(int acceptfd,MSG* msg,char word[]){
    FILE* fp;
    char temp[512]={0};
    int result;
    char *p;
    int len=strlen(word);
    if((fp=fopen("dict.txt","r"))==NULL){
        memset(msg->text,0,sizeof(msg->text));
        strcpy(msg->text,"打开文件失败");
        if(send(acceptfd,msg,sizeof(MSG),0)==-1){
            ERRLOG("send error");
        }
        ERRLOG("fopen error");
    }

    while(fgets(temp,512,fp)!=NULL){
        result=strncmp(word,temp,len);

        if(result>0){
            continue;
        }

        if(result<0||temp[len]!=' '){
            break;
        }

        p=temp+len;

        while(*p==' '){

            p++;

        }

        strcpy(msg->text,p);

        return 1;

    }

    return 0;
}

void do_time(char Time[]){
    struct tm *tp;
    time_t t;

    time(&t);

    tp=localtime(&t);

    sprintf(Time,"%d:%d:%d,%d:%d:%d",tp->tm_year+1900,tp->tm_mon+1,tp->tm_mday,tp->tm_hour,tp->tm_sec,tp->tm_min);

}

void do_history(int acceptfd,MSG* msg,sqlite3* db){
    char sql[128]={0};
    char * errmsg;

    sprintf(sql,"select * from record where name='%s';",msg->name);

    if(sqlite3_exec(db,sql,history_callback,(void*)&acceptfd,&errmsg)!=SQLITE_OK){
        ERRLOG("sqlite3_exec error");
    }

    memset(msg->text,0,sizeof(msg->text));
    msg->text[0]='\0';
    if(send(acceptfd,msg,sizeof(MSG),0)==-1){
        ERRLOG("send error");
    }
}

int history_callback(void* arg,int ncolumn,char** values,char** name){
    int acceptfd;
    acceptfd=*((int*)arg);

    MSG msg;
    sprintf(msg.text,"%s , %s",values[1],values[2]);

    if(send(acceptfd,&msg,sizeof(MSG),0)==-1){
        ERRLOG("send error");
    }

    return 0;
}


void* pthread_client(void* arg){

    pthread_detach(pthread_self());
    struct client value=*((struct client*)arg);
    do_client(value.acceptfd,value.db);

    return NULL;
}